﻿using Microsoft.AspNetCore.Mvc;
using Newtonsoft.Json;
using Nop.Core;
using Nop.Core.Configuration;
using Nop.Core.Infrastructure;
using Nop.Services.Catalog;
using Nop.Services.Media;
using Nop.Web.Areas.Admin.Models.Catalog;
using Nop.Web.Framework.Mvc.Filters;
using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Threading.Tasks;
using Xabe.FFmpeg;
using Xabe.FFmpeg.Enums;
using Xabe.FFmpeg.Model;

namespace Nop.Web.Areas.Admin.Controllers
{
    public class VideoController : BaseAdminController
    {
        #region Fields

        private readonly IDownloadService _downloadService;
        private readonly INopFileProvider _fileProvider;
        private readonly IProductService _productService;
        private readonly IWebHelper _webHelper;
        private readonly NopConfig _config;
        #endregion

        #region Ctor

        public VideoController(IDownloadService downloadService,
            INopFileProvider fileProvider,
            IProductService productService,
            IWebHelper webHelper,
            NopConfig config)
        {
            this._downloadService = downloadService;
            this._fileProvider = fileProvider;
            this._productService = productService;
            this._webHelper = webHelper;
            this._config = config;
        }

        #endregion

        #region Methods

        [HttpPost]
        //do not validate request token (XSRF)
        [AdminAntiForgery(true)]
        public async Task<IActionResult> AsyncUpload()
        {

            //if (!_permissionService.Authorize(StandardPermissionProvider.UploadPictures))
            //    return Json(new { success = false, error = "You do not have required permissions" }, "text/plain");

            var httpPostedFile = Request.Form.Files.FirstOrDefault();
            if (httpPostedFile == null)
            {
                return Json(new
                {
                    success = false,
                    message = "No file uploaded",
                    downloadGuid = Guid.Empty
                });
            }

           

            const string qqFileNameParameter = "qqfilename";
            var fileName = httpPostedFile.FileName;
            if (string.IsNullOrEmpty(fileName) && Request.Form.ContainsKey(qqFileNameParameter))
                fileName = Request.Form[qqFileNameParameter].ToString();
            //remove path (passed in IE)
            fileName = _fileProvider.GetFileName(fileName);

            var contentType = httpPostedFile.ContentType;

            var fileExtension = _fileProvider.GetFileExtension(fileName);
            if (!string.IsNullOrEmpty(fileExtension))
                fileExtension = fileExtension.ToLowerInvariant();

            //contentType is not always available 
            //that's why we manually update it here
            //http://www.sfsu.edu/training/mimetype.htm
            if (!string.IsNullOrEmpty(fileExtension))
            {
                switch (fileExtension)
                {
                    case ".flv":
                        break;
                    case ".mp4":
                        break;
                    case ".avi":
                        break;
                    default:
                        return Json(new
                        {
                            success = false,
                            message = "文件类型为mp4,flv,avi",
                            downloadGuid = Guid.Empty
                        });
                }
            }
            var newFileName = $"{Guid.NewGuid().ToString("D")}_{fileName}";
            var tempVideoFile = Path.Combine("video", "temp", newFileName);
            var tempCoverFile = Path.Combine("video", "temp", $"{ Path.GetFileNameWithoutExtension(newFileName)}.Png");
            var tempVideoFilePath = _fileProvider.GetAbsolutePath(tempVideoFile);
            var tempCoverFilePath = _fileProvider.GetAbsolutePath(tempCoverFile);
            if (!_fileProvider.DirectoryExists(Path.GetDirectoryName(tempVideoFilePath)))
            {
                _fileProvider.CreateDirectory((Path.GetDirectoryName(tempVideoFilePath)));
            }
            using (var readStream = httpPostedFile.OpenReadStream())
            {
                using (FileStream writeStream = new FileStream(tempVideoFilePath, FileMode.OpenOrCreate, FileAccess.Write))
                {
                    byte[] buffer = new byte[1024];
                    while (true)
                    {
                        var readLength = readStream.Read(buffer, 0, buffer.Length);
                        if (readLength < 1) break;
                        writeStream.Write(buffer, 0, readLength);
                        if (readLength < buffer.Length) break;
                    }
                    writeStream.Flush();
                }
            }
            if (!string.IsNullOrEmpty(_config.FFmpegExecutablePath))
            {
                FFmpeg.ExecutablesPath = _config.FFmpegExecutablePath;
            }

            IMediaInfo mediaInfo = await MediaInfo.Get(tempVideoFilePath);
            var videoStream = mediaInfo.VideoStreams.FirstOrDefault();
            IConversionResult result = await new Conversion().AddStream(videoStream.SetCodec(VideoCodec.Png).SetOutputFramesCount(1)).
                SetOutput(tempCoverFilePath).Start();
            if (!result.Success)
            {
                _fileProvider.DeleteFile(tempVideoFilePath);
                _fileProvider.DeleteFile(tempCoverFilePath);
                return Json(new
                {
                    success = false,
                    message = "无法获取视频截图",
                    downloadGuid = Guid.Empty
                });
            } 
            int width = videoStream.Width;
            int height = videoStream.Height; 
            int duration = Convert.ToInt32(mediaInfo.Duration.TotalSeconds);
            long size = mediaInfo.Size;
            var videoFile = Path.Combine("video", newFileName);
            var coverFile = Path.Combine("video", $"{Path.GetFileNameWithoutExtension(newFileName)}.Png");
            string videoPath = _fileProvider.GetAbsolutePath(videoFile);
            string coverPath = _fileProvider.GetAbsolutePath(coverFile);
            _fileProvider.FileMove(tempVideoFilePath, videoPath);
            _fileProvider.FileMove(tempCoverFilePath, coverPath);
            UriBuilder uriBuilder = new UriBuilder(_webHelper.GetStoreLocation());
            uriBuilder.Path = videoFile;
            string videoUrl = uriBuilder.Uri.ToString();
            uriBuilder.Path = coverFile;
            string coverUrl = uriBuilder.Uri.ToString();



            //when returning JSON the mime-type must be set to text/plain
            //otherwise some browsers will pop-up a "Save As" dialog.
            return Json(new { success = true, videoUrl = videoUrl, coverUrl = coverUrl, duration = duration, width = width, height = height, size = size });
        }

        #endregion

    }
}
